package cn.virens;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.tio.core.ChannelContext;
import org.tio.core.DefaultAioListener;
import org.tio.core.intf.Packet;

import cn.virens.app.common.SQL;
import cn.virens.exception.ReconnectException;
import cn.virens.exception.TimeoutException;

public class TioListener extends DefaultAioListener {
	private static final Logger logger = LoggerFactory.getLogger(TioListener.class);

	@Override
	public void onAfterConnected(ChannelContext channelContext, boolean isConnected, boolean isReconnect) {
		logger.debug("已连接({})-成功:{}", TioUtil.name(channelContext), isConnected);
		logger.debug("已连接({})-重连:{}", TioUtil.name(channelContext), isReconnect);
	}

	@Override
	public void onAfterReceivedBytes(ChannelContext channelContext, int receivedBytes) throws Exception {
		logger.debug("总接收({})-长度:{} bytes", TioUtil.name(channelContext), receivedBytes);
	}

	@Override
	public void onAfterDecoded(ChannelContext channelContext, Packet packet, int packetSize) {
		logger.debug("已接收({})-长度:{} bytes", TioUtil.name(channelContext), packetSize);
		logger.debug("已接收({})-数据:{}", TioUtil.name(channelContext), String.valueOf(packet));
	}

	@Override
	public void onAfterSent(ChannelContext channelContext, Packet packet, boolean isSentSuccess) throws Exception {
		logger.debug("已发送({})-成功:{}", TioUtil.name(channelContext), isSentSuccess);
		logger.debug("已发送({})-数据:{}", TioUtil.name(channelContext), String.valueOf(packet));
	}

	@Override
	public void onAfterHandled(ChannelContext channelContext, Packet packet, long cost) throws Exception {
		logger.debug("已处理({})-数据:{}", TioUtil.name(channelContext), String.valueOf(packet));
		logger.debug("已处理({})-耗时:{} ms", TioUtil.name(channelContext), cost);
	}

	@Override
	public void onBeforeClose(ChannelContext channelContext, Throwable throwable, String remark, boolean isRemove) {
		logger.debug("已断开({})-成功:{}", TioUtil.name(channelContext), isRemove);

		if (throwable instanceof ReconnectException) {
			logger.debug("已断开({})-重连:{}-{}", TioUtil.name(channelContext), remark, throwable.getMessage());
		} else if (throwable instanceof TimeoutException) {
			logger.debug("已断开({})-连接超时:{}", TioUtil.name(channelContext), String.valueOf(remark));
			this.doOffline(channelContext, "设备掉线（连接超时）");
		} else {
			logger.debug("已断开({})-备注:{}", TioUtil.name(channelContext), String.valueOf(remark));
			logger.debug("已断开({})-异常:{}-->message:{}-->cause:{}-->localizedmsg:{}", TioUtil.name(channelContext), String.valueOf(throwable), throwable.getMessage(), throwable.getCause(), throwable.getLocalizedMessage());

			this.doOffline(channelContext, "设备掉线（异常掉线）--------->" + throwable.getMessage());
		}
		logger.debug("-----------------------------------------------");
		throwable.printStackTrace();
	}

	private void doOffline(ChannelContext channelContext, String remark) {
		App.db().executeUpdate(SQL.OFF_LINE, TioUtil.imei(channelContext));
		App.db().executeUpdate(SQL.ONLINE_STATUS_UP, 0, TioUtil.imei(channelContext));
		App.db().executeUpdate(SQL.RECORD_IN, TioUtil.imei(channelContext), 2, remark);
		App.device().channelUnbind(channelContext);
	}
}
